//***************************************************************//
//*																*//
//*  Copyright (C) 1999 Virtue 3D, Inc.   All Rights Reserved.	*//
//*																*//
//*  File:	   vrNode.h											*//
//*  Content:  VR nodes header file								*//
//*  Date:     July 26, 1999									*//
//*																*//
//***************************************************************//
#ifndef  _VR_NODE_
#define  _VR_NODE_

#include "VRField.h"


class VRNode;
class VRGroup;
class VRTransform;
class VRLOD;
class VRShape;
class VRAppearance;
class VRMaterial;
class VRTexture;
class VRImageTexture;
class VRTextureTransform;
class VRGeometry;
class VRIndexedFaceSet;
class VRCoordinate;
class VRTextureCoordinate;
class VRColor;
class VRNormal;
class VRMatrix;
class VRViewpoint;
class VRLight;
class VRDirectionalLight;
class VRPointLight;
class VRSpotLight;
class VRAudioClip;
class VRSound;


class VRNode
{
public:
	VRNode(void);
	virtual ~VRNode(void);

	virtual void release(void);
	void copy (VRNode *src);
	VRResult getNodesOfType (VRNodeType type, VRMFNode &nodes);
	VRResult getMorphShapes (VRMFDWORD &shapeId);
	VRResult transformShapes (VRShape ***shapes, VRDWORD &numShapes, VRSFBool makeCopy);
	VRResult uniteGeometry (VRShape **shape);
	static VRResult releaseAuxiliaryMemory ();

	VRNode*    parent;
	VRSFString name;
	VRDWORD    referenceCount;
	VRNodeType type;

	void* userData;
	typedef void (*creationCallBackType) (VRNode* arg);
	typedef void (*copyCallBackType) (VRNode* dest,VRNode* src);
	typedef void (*deletionCallBackType) (VRNode* arg);

	static creationCallBackType creationCallBack;
	static copyCallBackType copyCallBack;
	static deletionCallBackType deletionCallBack;

private:
	int getTransformShapes( VRMFNode &head, VRDWORD *vindex, VRSFMat44f &tmat, VRSFBool makeCopy);
	int getShapes( VRMFNode &head, VRDWORD &vindex);
};

class VRGroup: public VRNode
{
public:
	VRGroup(void);
	virtual void release(void);
	void copy(VRGroup* src);

	VRMFNode  children;
};

class VRTransform: public VRGroup
{
public:
	VRTransform(void);
	void copy(VRTransform* src);
	VRResult  reset();

	VRSFVec3f    translation;
	VRSFRotation rotation;
	VRSFVec3f    scale;
	VRSFRotation scaleOrientation;
	VRSFVec3f    center;
};

class VRLOD: public VRGroup
{
public:
	VRLOD(void);
	virtual void release(void);
	void copy(VRLOD* src);

	VRSFVec3f center;
	VRMFFloat range;
};

class VRShape: public VRNode
{
public:
	VRShape(void);
	virtual void release(void);
	VRResult decompose(VRShape** shape1, VRShape** shape2);
	
	void copy(VRShape* src);
	VRShape* transformShape( VRSFMat44f mat, VRSFBool makeCopy);
	void applyTextureTransform();

	VRAppearance* appearance;
	VRGeometry*   geometry;
};

class VRAppearance: public VRNode
{
public:
	VRAppearance(void);
	virtual void release(void);
	void copy(VRAppearance* src);

	VRMaterial         *material;
	VRTexture          *texture;
	VRTextureTransform *textureTransform;
};

class VRMaterial: public VRNode
{
public:
	VRMaterial(void);
	void copy(VRMaterial* src);

	VRSFColor diffuseColor;
	VRSFFloat ambientIntensity;
	VRSFColor specularColor;
	VRSFColor emissiveColor;
	VRSFFloat shininess;
	VRSFFloat transparency;
	VRSFFloat reflection;
};

class VRTexture: public VRNode
{
public:
	VRTexture(void);
	void copy(VRTexture* src);

	VRSFBool repeatS;
	VRSFBool repeatT;
};

class VRImageTexture: public VRTexture
{
public:
	VRImageTexture(void);
	void copy(VRImageTexture* src);
	virtual void release(void);

	VRMFString url;
};

class VRTextureTransform: public VRNode
{
public:
	VRTextureTransform(void);
	void copy(VRTextureTransform* src);
	void apply(VRSFVec2f);

	VRSFVec2f translation;
	VRSFFloat rotation;
	VRSFVec2f scale;
	VRSFVec2f center;
};

class VRGeometry: public VRNode
{
public:
	VRGeometry(void);

	virtual bool getBoundingBox(VRSFVec3f bottom, VRSFVec3f top) = 0;
	virtual void applyTextureTransform(VRTextureTransform*) = 0;
};


class VRCoordinate: public VRNode
{
public:
	VRCoordinate(void);
	virtual void release(void);
	void copy(VRCoordinate * src);

	VRMFVec3f point;
};

class VRTextureCoordinate: public VRNode
{
public:
	VRTextureCoordinate(void);
	virtual void release(void);
	void copy(VRTextureCoordinate * src);

	VRMFVec2f point;
};

class VRColor: public VRNode
{
public:
	VRColor(void);
	virtual void release(void);
	void copy(VRColor * src);

	VRMFColor color;
};

class VRNormal: public VRNode
{
public:
	VRNormal(void);
	virtual void release(void);
	void copy(VRNormal * src);

	VRMFVec3f vector;
};

class VRViewpoint: public VRNode
{
public:
	VRViewpoint(void);
	virtual void release();
	void copy(VRViewpoint * src);

	VRSFVec3f    position;
	VRSFRotation orientation;
	VRSFFloat    fieldOfView;
	VRSFString   description;
};

class VRLight: public VRNode
{
public:
	VRLight(void);
	void copy(VRLight * src);

	VRSFBool	on;
	VRSFFloat	intensity;
	VRSFFloat	ambientIntensity;
	VRSFColor	color;
};

class VRDirectionalLight: public VRLight
{
public:
	VRDirectionalLight(void);
	void copy(VRDirectionalLight * src);

	VRSFVec3f	direction;
};

class VRPointLight: public VRLight
{
public:
	VRPointLight(void);
	void copy(VRPointLight * src);

	VRSFVec3f	location;
	VRSFFloat	radius;
	VRSFVec3f	attenuation;
};

class VRSpotLight: public VRLight
{
public:
	VRSpotLight(void);
	void copy(VRSpotLight *src);

	VRSFVec3f	location;
	VRSFVec3f	direction;
	VRSFFloat	beamWidth;
	VRSFFloat	cutOffAngle;
	VRSFFloat	radius;
	VRSFVec3f	attenuation;
};

class VRAudioClip: public VRNode
{
public:
	VRAudioClip(void);
	virtual void release(void);
	void copy(VRAudioClip* src);

	VRSFString	description;
	VRSFBool	loop;
	VRSFFloat	pitch;
	VRSFTime	startTime;
	VRSFTime	stopTime;
	VRMFString	url;
};

class VRSound: public VRNode
{
public:
	VRSound(void);
	virtual void release(void);
	void copy(VRSound* src);

	VRNode		*source;
	VRSFFloat	intensity;
	VRSFFloat	priority;
	VRSFVec3f	location;
	VRSFVec3f	direction;
	VRSFFloat	minFront;
	VRSFFloat	maxFront;
	VRSFFloat	minBack;
	VRSFFloat	maxBack;
	VRSFBool	spatialize;
};

VRNode* Clone(VRNode*);

#endif	// _VR_NODE_
